package com.utils.socket.mychanel;

import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;

/**
 * Created by apple on 2017/4/23.
 */
public class Server {
    private List<MyChanel> all = new ArrayList<MyChanel>();

    public static void main(String[] args) throws IOException {
        new Server().start();
    }

    public void start() throws IOException {
        ServerSocket server = new ServerSocket(9999);
        while (true) {
            Socket client = server.accept();
            MyChanel channel = new MyChanel(client);
            all.add(channel);//加入到容器中同意管理
            new Thread(channel).start();//一条道路
        }
    }

    /**
     * 一个客户端一个道路
     * 1 输入流
     * 2 输出流
     * 3 接收数据
     * 4 发送数据
     *
     * @author lyy
     */
    private class MyChanel implements Runnable {
        private DataInputStream dis;
        private DataOutputStream dos;
        private boolean isRunning = true;
        private String name;

        public MyChanel(Socket client) {
            try {
                dis = new DataInputStream(client.getInputStream());
                dos = new DataOutputStream(client.getOutputStream());

                this.name = dis.readUTF();
                this.send("欢迎你进入聊天室！");
                sendOthers(this.name + "进入了聊天室", true);
            } catch (IOException e) {
                CloseUtil.closeAll(dis, dos);
                isRunning = false;
            }

        }

        /**
         * 读取数据
         *
         * @return
         */
        private String receive() {
            String msg = "";
            try {
                msg = dis.readUTF();
            } catch (IOException e) {
                CloseUtil.closeAll(dis);
                isRunning = false;
                all.remove(this);//移除自身
            }
            return msg;
        }

        /**
         * 发送数据
         */
        public void send(String msg) {
            if (null == msg && !msg.equals("")) {
                return;
            }
            try {
                dos.writeUTF(msg);
                dos.flush();
            } catch (IOException e) {
//              e.printStackTrace();
                CloseUtil.closeAll(dos);
                isRunning = false;
                all.remove(this);//移除自身
            }
        }

        /**
         * 发送给其他客户端
         */
        private void sendOthers(String msg, boolean sys) {
            System.out.println(msg);
            //是否为私聊 约定
            if (msg.startsWith("@") && msg.indexOf(":") > -1) {//表示私聊
                String name = msg.substring(1, msg.indexOf(":"));
                String conetnt = msg.substring(msg.indexOf(":") + 1);
                //获取Name
                for (MyChanel other : all) {
                    if (other.name.equals(name)) {
                        other.send(this.name + "对您悄悄说" + conetnt);
                    }
                }
            } else {

                //遍历容器
                for (MyChanel other : all) {
                    if (other == this) {
                        continue;
                    }
                    if (sys) {//系统信息
                        //发送给其他客户端
                        other.send("系统信息：" + msg);
                    } else {
                        //发送给其他客户端
                        other.send(this.name + "：" + msg);
                    }

                }
            }
        }

        public void run() {
            while (isRunning) {
                sendOthers(receive(), false);
            }
        }

    }
}
